package cn.shop.admin.service.impl;

import cn.hutool.core.util.StrUtil;
import cn.shop.admin.entity.excel.FrontUserExcel;
import cn.shop.admin.mapper.FrontUserMapper;
import cn.shop.admin.req.FrontUserQueryReq;
import cn.shop.admin.service.FrontUserService;
import cn.shop.base.MyPage;
import cn.shop.base.MyServiceImpl;
import cn.shop.transcation.alipay.entity.AlipayAccount;
import cn.shop.transcation.alipay.mapper.AlipayAccountMapper;
import cn.shop.transcation.bankcard.entity.BankCard;
import cn.shop.transcation.bankcard.mapper.BankCardMapper;
import cn.shop.transcation.detail.entity.TransactionDetail;
import cn.shop.transcation.frontUserModule.FrontUser;
import cn.shop.utils.Putif;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.stereotype.Service;

import javax.annotation.Resource;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors;

import static cn.shop.utils.QueryUtil.columnToString;

/**
 * 购物平台用户表(FrontUser)表服务实现类
 *
 * @author jzw
 * @since 2022-02-23 09:39:05
 */
@Service("frontUserService")
public class FrontUserServiceImpl extends MyServiceImpl<FrontUserMapper, FrontUser> implements FrontUserService {

	private static final Logger LOG = LoggerFactory.getLogger(FrontUserServiceImpl.class);

	@Resource
	private FrontUserMapper frontUserMapper;
	@Resource
	private BankCardMapper bankCardMapper;
	@Resource
	private AlipayAccountMapper alipayAccountMapper;

	/**
	 * 查询玩家绑定的游戏角色
	 *
	 * @param id
	 * @return
	 * @author jzw
	 * @since 2022/2/26 16:32
	 */
	@Override
	public List<Map<String, Object>> queryAllRole(Long id) {
		return baseMapper.queryAllRole(id);
	}

	@Override
	public MyPage<TransactionDetail> queryRecordByPage(MyPage<TransactionDetail> page, Long id) {
		return baseMapper.queryRecordByPage(page, id);
	}

	@Override
	public Map<String, Object> bindAccountList(long uid) {
		List<BankCard> cards = bankCardMapper.selectList(Wrappers.<BankCard>lambdaQuery()
				.eq(BankCard::getOwnerId, uid));
		List<AlipayAccount> accounts = alipayAccountMapper.selectList(Wrappers.<AlipayAccount>lambdaQuery()
				.eq(AlipayAccount::getOwnerId, uid));
		return Putif.start()
				.anyway("bank", cards.stream().map(this::format).collect(Collectors.toList()))
				.anyway("alipay", accounts.stream().map(this::format).collect(Collectors.toList()))
				.get();
	}

	@Override
	public List<FrontUserExcel> allUser() {
		// 2023/3/27 优化查询 直接用链表sql 代替循环连接数据库
		return frontUserMapper.selectAllByExcel();
//		List<FrontUser> all = list();
//		return all.stream()
//				.map(this::parse)
//				.flatMap(Collection::stream)
//				.collect(Collectors.toList());
	}

	@Override
	public MyPage<FrontUser> queryFrontUser(MyPage<FrontUser> page, FrontUserQueryReq req) {
		if (req.getStartTime() != null) {
			req.setStartTime(req.getStartTime().withSecond(0));
		}
		if (req.getEndTime() != null) {
			req.setEndTime(req.getEndTime().withSecond(59));
		}
		if (StrUtil.isNotBlank(req.getPlayerAccount()) || StrUtil.isNotBlank(req.getPlayerNickname())) {
			return baseMapper.queryByPlayer(page, req);
		}
		QueryWrapper<FrontUser> queryWrapper = Wrappers.<FrontUser>query()
				.eq(req.getAdvanced() != null, columnToString(FrontUser::getAdvanced), req.getAdvanced())
				.eq(StrUtil.isNotBlank(req.getPhone()), columnToString(FrontUser::getPhone), req.getPhone())
				.eq(StrUtil.isNotBlank(req.getAccount()), columnToString(FrontUser::getAccount), req.getAccount())
				.eq(StrUtil.isNotBlank(req.getName()), columnToString(FrontUser::getName), req.getName())
				//.apply(req.getStartTime() != null,
				//		"date_format (" + columnToString(FrontUser::getCreateTime) + ",'%Y-%m-%d %H:%i') >= date_format ({0},'%Y-%m-%d %H:%i')", req.getStartTime().withSecond())
				//.apply(req.getEndTime() != null,
				//		"date_format (" + columnToString(FrontUser::getCreateTime) + ",'%Y-%m-%d %H:%i') <= date_format ({0},'%Y-%m-%d %H:%i')", req.getEndTime())
				.gt(req.getStartTime() != null,columnToString(FrontUser::getCreateTime), req.getStartTime())
				.lt(req.getEndTime() != null, columnToString(FrontUser::getCreateTime), req.getEndTime())
				.select(columnToString(FrontUser::getId), columnToString(FrontUser::getAccount),
						columnToString(FrontUser::getRisk), columnToString(FrontUser::getPhone),
						columnToString(FrontUser::getName), columnToString(FrontUser::getBalance),
						columnToString(FrontUser::getAdvanced), columnToString(FrontUser::getCertification),
						"INSERT( identity_card,4,11,'***********' ) " + columnToString(FrontUser::getIdentityCard),
						columnToString(FrontUser::getAvatar), columnToString(FrontUser::getLastLoginTime), columnToString(FrontUser::getCreateTime));
		if (Boolean.TRUE.equals(req.getOrderByBalance())) {
			queryWrapper.orderByDesc(columnToString(FrontUser::getBalance));
		} else {
			queryWrapper.orderByDesc(columnToString(FrontUser::getId));
		}
		return page(page, queryWrapper);
	}

	private List<FrontUserExcel> parse(FrontUser user) {
		List<BankCard> cards = bankCardMapper.selectList(Wrappers.<BankCard>lambdaQuery()
				.eq(BankCard::getOwnerId, user.getId()));
		List<AlipayAccount> accounts = alipayAccountMapper.selectList(Wrappers.<AlipayAccount>lambdaQuery()
				.eq(AlipayAccount::getOwnerId, user.getId()));
		List<FrontUserExcel> list = new ArrayList<>();
		if (!cards.isEmpty() || !accounts.isEmpty()) {
			list.addAll(cards.stream()
					.map(c -> createModel(user, c))
					.collect(Collectors.toList()));
			list.addAll(accounts.stream()
					.map(a -> createModel(user, a))
					.collect(Collectors.toList()));
		} else {
			list.add(createModel(user));
		}
		return list;
	}

	private FrontUserExcel createModel(FrontUser user, BankCard card) {
		return createModel(user)
				.setBankName(card.getBankName())
				.setCardNo(card.getCardNo());
	}

	private FrontUserExcel createModel(FrontUser user, AlipayAccount account) {
		return createModel(user)
				.setAliAccount(account.getAccount());
	}

	private FrontUserExcel createModel(FrontUser user) {
		return new FrontUserExcel()
				.setAccount(user.getAccount())
				.setName(user.getName())
				.setGender(user.getGender() == null ? "" : user.getGender() ? "女" : "男")
				.setPhone(user.getPhone())
				.setBalance(user.getBalance())
				.setIdentityCard(user.getIdentityCard());

	}

	private Map<String, Object> format(BankCard bankCard) {
		return Putif.start()
				.anyway("bankName", bankCard.getBankName())
				.anyway("cardNo", bankCard.getCardNo())
				.get();
	}

	private Map<String, Object> format(AlipayAccount account) {
		return Putif.start()
				.anyway("account", account.getAccount())
				.get();
	}
}

